import type { RuntimeBullet, DanmakuConfig } from '../types';

export interface CanvasRendererOptions {
  canvas: HTMLCanvasElement;
  config: DanmakuConfig;
}

export class CanvasRenderer {
  private canvas: HTMLCanvasElement;
  private ctx: CanvasRenderingContext2D;
  private config: DanmakuConfig;
  private dpr = 1;

  constructor(options: CanvasRendererOptions) {
    this.canvas = options.canvas;
    const ctx = this.canvas.getContext('2d');
    if (!ctx) throw new Error('Canvas 2D context not available');
    this.ctx = ctx;
    this.config = options.config;
    this.updateDPR();
  }

  updateDPR() {
    this.dpr = this.config.dprAware ? Math.max(1, Math.floor(window.devicePixelRatio || 1)) : 1;
  }

  resize(width: number, height: number) {
    const cssWidth = Math.max(1, Math.floor(width));
    const cssHeight = Math.max(1, Math.floor(height));
    const pixelWidth = cssWidth * this.dpr;
    const pixelHeight = cssHeight * this.dpr;
    if (this.canvas.width !== pixelWidth || this.canvas.height !== pixelHeight) {
      this.canvas.width = pixelWidth;
      this.canvas.height = pixelHeight;
      this.canvas.style.width = cssWidth + 'px';
      this.canvas.style.height = cssHeight + 'px';
    }
  }

  clear() {
    this.ctx.clearRect(0, 0, this.canvas.width, this.canvas.height);
  }

  draw(bullets: RuntimeBullet[]) {
    const ctx = this.ctx;
    ctx.save();
    ctx.globalAlpha = this.config.opacity;
    ctx.textBaseline = 'middle';
    for (const b of bullets) {
      const font = `${Math.round(b.fontSize * this.dpr)}px ${this.config.fontFamily}`;
      ctx.font = font;
      const x = Math.round(b.x * this.dpr);
      const y = Math.round(b.y * this.dpr);
      if (this.config.enableStroke) {
        ctx.lineWidth = Math.max(2, Math.floor(3 * this.dpr));
        ctx.strokeStyle = 'rgba(0,0,0,0.7)';
        ctx.strokeText(b.text, x, y);
      }
      ctx.fillStyle = b.color;
      ctx.fillText(b.text, x, y);
    }
    ctx.restore();
  }
}


